package com.anzym.android.kegdroidkey;

import com.anzym.android.kegdroidkey.auth.PlusScopes;
import com.anzym.android.kegdroidkey.tasks.GetPlusPersonDataTask;
import com.anzym.android.kegdroidlibrary.models.KegDroidUser;
import com.anzym.android.kegdroidlibrary.tasks.Utils;
import com.anzym.android.kegdroidlibrary.tasks.FetchKegDroidUser;
import com.anzym.android.kegdroidlibrary.tasks.OnTaskCompleted;
import com.google.android.gms.common.ConnectionResult;
import com.google.android.gms.common.GooglePlayServicesClient.ConnectionCallbacks;
import com.google.android.gms.common.GooglePlayServicesClient.OnConnectionFailedListener;
import com.google.android.gms.common.GooglePlayServicesUtil;
import com.google.android.gms.plus.PlusClient;

import org.json.JSONObject;

import android.app.ProgressDialog;
import android.content.Intent;
import android.content.IntentSender.SendIntentException;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentManager;
import android.util.Log;
import android.view.View;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;

public class DrinkerLoginActivity extends FragmentActivity implements View.OnClickListener,
        ConnectionCallbacks, OnConnectionFailedListener {

    private String TAG = DrinkerLoginActivity.class.getSimpleName();

    KegDroidKeyApplication keyApp;
    
    private static final String TAG_ERROR_DIALOG_FRAGMENT = "errorDialog";
    private static final int REQUEST_CODE_RESOLVE_FAILURE = 9000;
    private static final int REQUEST_CODE_RESOLVE_MISSING_GP = 9001;
    
    private static final int REQUEST_CODE_EXIT_APP = 8000;
    private static final int SIGNED_IN = 8001;
    private static final int LOGGED_OUT = 8002;
    
    private ProgressDialog mConnectionProgressDialog;
    private PlusClient mPlusClient;
    private ConnectionResult mStatus;
    private TextView mSignInStatus;

    private GetPlusPersonDataTask mAsyncTask;
    private FetchKegDroidUser mFetchUserTask;
    private OnTaskCompleted fetchCompleteListener;

    private String emailAddress;
    private String gPlusId;
 
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.drinker_login);

        keyApp = KegDroidKeyApplication.getInstance();
        mPlusClient = new PlusClient.Builder(this, this, this)
        .setActions("http://schemas.google.com/AddActivity", "http://schemas.google.com/BuyActivity")
        .build();

        // Spinner progress bar to be displayed if the user clicks the Google+
        // sign-in button before resolving connection errors.
        mConnectionProgressDialog = new ProgressDialog(DrinkerLoginActivity.this);
        mConnectionProgressDialog.setMessage(getString(R.string.signing_in_status));
        mConnectionProgressDialog.setOwnerActivity(DrinkerLoginActivity.this);

        findViewById(R.id.sign_in_button).setOnClickListener(this);
        findViewById(R.id.sign_out_button).setOnClickListener(this);
        findViewById(R.id.exit_button).setOnClickListener(this);

        mSignInStatus = (TextView) findViewById(R.id.sign_in_status);

        fetchCompleteListener = new OnTaskCompleted() {

            @Override
            public void onTaskCompleted() {
                Log.d(TAG, "User Fetch Complete");
                DrinkerLoginActivity.this.setResult(SIGNED_IN);
                DrinkerLoginActivity.this.finish();

            }
        };
        emailAddress = keyApp.getUser().getEmailAddress();
        gPlusId = keyApp.getUser().getGPlusId();
        Log.d(TAG, "email: " + emailAddress + "  gplusId: " + gPlusId);

    }

    @Override
    protected void onStart() {
        super.onStart();
        mPlusClient.connect();
        mSignInStatus.setText(getString(R.string.loading_status));
    }

    @Override
    protected void onStop() {
        super.onStop();
        mPlusClient.disconnect();
        if (mAsyncTask != null) {
            mAsyncTask.cancel(false);
            mAsyncTask = null;
        }
    }

    public void onConnectionFailed(ConnectionResult status) {
        Log.d(TAG, "Failure Status: " + status);
        resetAccountState();
        if (mConnectionProgressDialog.isShowing()) {
            // The user clicked the button already and we are showing a spinner
            // progress dialog. We dismiss the progress dialog and start to
            // resolve connection errors.
            mConnectionProgressDialog.dismiss();
            Toast.makeText(this, "Failure Status:" + status, Toast.LENGTH_LONG).show();
            if (status.hasResolution()) {
                Log.d(TAG, "Failure Status has resolution: ");
                try {
                    status.startResolutionForResult(this, REQUEST_CODE_RESOLVE_FAILURE);
                } catch (SendIntentException e) {
                    mPlusClient.connect();
                }
            }
        }
        mStatus = status;
        FragmentManager fragmentManager = getSupportFragmentManager();
        if (!status.hasResolution()
                && GooglePlayServicesUtil.isUserRecoverableError(status.getErrorCode())
                && fragmentManager.findFragmentByTag(TAG_ERROR_DIALOG_FRAGMENT) == null) {
            GooglePlayServicesErrorDialogFragment.create(status.getErrorCode(),
                    REQUEST_CODE_RESOLVE_MISSING_GP).show(fragmentManager,
                    TAG_ERROR_DIALOG_FRAGMENT);
        }

    }

    @Override
    protected void onActivityResult(int requestCode, int responseCode, Intent intent) {
        switch (requestCode) {
            case REQUEST_CODE_RESOLVE_FAILURE:
            case REQUEST_CODE_RESOLVE_MISSING_GP:
                if (responseCode == RESULT_OK) {
                    mStatus = null;
                    mPlusClient.connect();
                } else {
                    Log.e(TAG, "Unable to recover from resolution attempt.");
                }
                break;
        }
    }

    public void onConnected(Bundle arg0) {
        String accountName = mPlusClient.getAccountName();
        Toast.makeText(this, accountName + " is connected.", Toast.LENGTH_LONG).show();

        mSignInStatus.setText(getString(R.string.signed_in_status));
        mConnectionProgressDialog.dismiss();

        if (mAsyncTask == null) {
            Log.d(TAG, "acctName: " + mPlusClient.getAccountName());
            mAsyncTask = new GetPlusPersonDataTask(this, mPlusClient.getAccountName()) {
                @Override
                protected void onPostExecute(JSONObject person) {
                    if (mPendingException != null) {
                        startActivityForResult(mPendingException.getIntent(),
                                REQUEST_CODE_RESOLVE_FAILURE);
                    }
                    if (person != null) {
                        final String name = person.optString("displayName", "unknown");
                        Log.d(TAG, "Display Name: " + name);
                        Log.d(TAG, "Fetching User Data");
                        mFetchUserTask = new FetchKegDroidUser(keyApp.getUser(),
                                fetchCompleteListener);
                        mFetchUserTask.execute(Utils.fetchUrl(getApplicationContext(),
                                person.optString("id", "unknown")));
                        keyApp.getUser().setEmailAddress(mPlusClient.getAccountName());
                        keyApp.getUser().setGPlusId(person.optString("id", "unknown"));
                        
                        keyApp.getUser().setDisplayName(person.optString("displayName", "unknown"));
                        keyApp.getUser().setImageUrl(person.optString("image", "unknown"));
                        
                        Log.d(TAG, "accountName: "+ keyApp.getUser().getEmailAddress());
                        Log.d(TAG, "gPlusId: "+ keyApp.getUser().getGPlusId());
                        Log.d(TAG, "displayNam: " + keyApp.getUser().getDisplayName());
                        Log.d(TAG, "imageUrl: " + keyApp.getUser().getImageUrl());
                    }
                    mAsyncTask = null;
                }
            };
            mAsyncTask.execute();
        }
    }

    public void onDisconnected() {
        //Do Nothing
    }

    public void onClick(View view) {

        switch (view.getId()) {
            case R.id.sign_in_button:
                Log.d(TAG, "Signing In");
                if (!mPlusClient.isConnected()) {
                    if (mStatus == null) {
                        mConnectionProgressDialog.show();
                    } else {
                        try {
                            mStatus.startResolutionForResult(this, REQUEST_CODE_RESOLVE_FAILURE);
                        } catch (SendIntentException e) {
                            // Try connecting again.
                            mStatus = null;
                            mPlusClient.connect();
                        }
                    }
                }
                break;
            case R.id.sign_out_button:
                keyApp.getUser().setEmailAddress(
                        getResources().getString(R.string.default_email));
                keyApp.getUser().setGPlusId(
                        getResources().getString(R.string.default_id));
                
                if (mPlusClient.isConnected()) {
                    resetAccountState();
                    mPlusClient.clearDefaultAccount();
                    mPlusClient.disconnect();
                    mPlusClient.connect();
                }
                setResult(LOGGED_OUT);
                this.finish();
                break;
            case R.id.exit_button:
                Log.d(TAG,"finish");
                setResult(REQUEST_CODE_EXIT_APP);
                this.finish();
                break;
        }
    }

    /**
     * Resets any pending calls to Google+ API and the user's sign-in status.
     */
    private void resetAccountState() {
        mSignInStatus.setText(getString(R.string.signed_out_status));

        // Reset cached state of any previous account that was signed in.
        if (mAsyncTask != null) {
            mAsyncTask.cancel(false);
            mAsyncTask = null;
        }
    }

}
